using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Diagnostics.Contracts;
using Konst3d.Efficiency.Suite;

namespace Konst3d.Efficiency.Suite.SparsedBinary
{
    internal interface IMonitorStorage
    {
        string Name
        {
            get;
            set;
        }

        string Description
        {
            get;
            set;
        }

        MonitorType Type
        {
            get;
        }

        int ID
        {
            get;
            set;
        }

        bool Active
        {
            get;
            set;
        }

        DateTime CreateDate
        {
            get;
        }

        IActiveDaysStorage ActiveDays
        {
            get;
        }

        IStatisticStorage Statistic
        {
            get;
        }

        void Delete();
    }

    internal class Monitor: IMonitor, IDisposable
    {
        #region IMonitor Members

        public int ID
        {
            get
            {
                return _storage.ID;
            }
        }

        public string Title
        {
            get
            {
                return _storage.Name;
            }
            set
            {
                _storage.Name = value;
            }
        }

        public string Description
        {
            get
            {
                return _storage.Description;
            }
            set
            {
                _storage.Description = value;
            }
        }

        public MonitorType Type
        {
            get
            {
                return _storage.Type;
            }
        }

        public bool Active
        {
            get
            {
                return _storage.Active;
            }
            set
            {
                _storage.Active = value;
            }
        }

        public DateTime Created
        {
            get
            {
                return _storage.CreateDate;
            }
        }

        public IMonitoringStatistic Statistic
        {
            get
            {
                return _statistic;
            }
        }

        public IMonitoringActiveDays ActiveDays
        {
            get
            {
                return _activeDays;
            }
        }

        public double GetAverageValue()
        {
            return _statistic.GetAverageValue();
        }

        public double GetAverageValue(DateTime start, DateTime end)
        {
            return _statistic.GetAverageValue(start, end);
        }

        public double GetSummaryValue()
        {
            return _statistic.GetSummaryValue();
        }

        public double GetSummaryValue(DateTime start, DateTime end)
        {
            return _statistic.GetSummaryValue(start, end);
        }

        public int GetCommandmentViolationsCount()
        {
            return _statistic.GetCommandmentViolationsCount();
        }

        public int GetCommandmentViolationsCount(DateTime start, DateTime end)
        {
            return _statistic.GetCommandmentViolationsCount(start, end);
        }

        #endregion

        #region Constructor/Finalizer

        public Monitor(MonitorStorage storage, MonitoringStatistic statistic, MonitoringActiveDays activeDays)
        {
            Contract.Requires(storage != null);
            Contract.Requires(statistic != null);
            Contract.Requires(activeDays != null);

            _storage = storage;
            _statistic = statistic;
            _activeDays = activeDays;
        }

        ~Monitor()
        {
            Dispose(false);
        }

        #endregion // Constructor/Finalizer

        #region Public Methods

        public void Delete()
        {
            Contract.Assert(!_disposed);

            _storage.Delete();

            Dispose();
        }

        #endregion // Public Methods

        #region IDisposable Members

        public void Dispose()
        {
            GC.SuppressFinalize(this);
            Dispose(true);
        }

        private void Dispose(bool disposing)
        {
            if (!_disposed)
            {
                if (disposing)
                {
                    _storage.Dispose();
                    _storage = null;

                    _statistic = null;
                    _activeDays = null;
                }

                _disposed = true;
            }
        }

        #endregion

        #region Fields

        private bool _disposed = false;
        private MonitorStorage _storage;
        private MonitoringStatistic _statistic;
        private MonitoringActiveDays _activeDays;

        #endregion // Fields
    }
}
